Compiler Hints

[[assume(expression)]] (C++23)

  • Gives optimizer a condition assumed to be true.

  • Undefined behavior if false at runtime.

[[assume(x > 0)]];
  • Low-level optimization hint.

  • Vendor equivalents (both languages):

    • __builtin_assume

    • __assume  (MSVC)

  • Used to eliminate bounds checks and unreachable branches.

_Static_assert (C11) / static_assert (C++11)

Compile-time assertion (not attribute).

_Static_assert(sizeof(int) == 4, "Unexpected size");

constexpr (C++11)

  • Allows evaluation at compile time.

  • The compiler may compute the result during compilation.

  • Used for:

    • lookup tables

    • compile-time constants

    • metaprogramming

constexpr int square(int x) {
    return x * x;
}
int a = square(4);

consteval (C++20)

  • .

constinit (C++20)

  • .

_Noreturn (C11), [[noreturn]] (C++11)

  • Indicates a function never returns.

[[noreturn]] void fatal();
  • They are semantic guarantees, not just documentation. They can affect code generation.

  • They state that a function:

    • never returns normally

    • either calls exit, abort, longjmp, or loops forever

    • reaching the end is undefined behavior

  • The compiler:

    • does not require a return

    • removes code after the call

    • may remove stack cleanup logic

restrict (C99)

  • For the lifetime of the pointer the object it points to is accessed only through that pointer (or a value directly derived from it).

  • Enables aliasing optimizations.

  • Tells compiler pointers do not alias.

  • Very significant in hot loops:

    • enables vectorization

    • enables load/store reordering

    • reduces reloads from memory

    • improves auto-SIMD generation

  • Without restrict, compiler must conservatively assume aliasing.

  • Incorrect use causes undefined behavior and real miscompilations.

void f(int * restrict p);
  • C++ has no standard equivalent (vendors support __restrict).

[[no_unique_address]] (C++20)

  • Allows a non-static data member (typically empty type) to occupy no storage.

struct Empty {};

struct S {
    int x;
    [[no_unique_address]] Empty e;
};
  • Without it:

    • e  may consume 1 byte

  • With it:

    • e  can overlap with padding

    • object size may shrink

  • Optimization impact

    • reduces object size

    • improves cache density

    • improves container packing

[[reproducible]] (C23)

  • Guarantees that the function:

    • has no observable side effects

    • depends only on its arguments and possibly global state

    • produces consistent results

[[reproducible]]
int pure_compute(int x);
  • Vendor equivalents in both languages:

    • __attribute__((pure))

  • Optimization impact

    • Allows:

      • common subexpression elimination

      • redundant call elimination

      • hoisting out of loops

      • reordering relative to unrelated side effects

  • The compiler may transform:

    int a = f(10);
    int b = f(10);
    
  • into:

    int a = f(10);
    int b = a;
    

[[unsequenced]] (C23)

  • Stronger than [[reproducible]].

  • Indicates:

    • no side effects

    • no synchronization

    • no inter-thread interaction

    • can be evaluated in unsequenced context

[[unsequenced]]
int fast_math(int x);
  • Vendor equivalents in both languages:

    • __attribute__((const))

  • Optimization impact

    • Allows:

      • aggressive reordering

      • call merging

      • vectorization

      • evaluation in arbitrary order

      • removal if result unused